package com.kds.fxtool.service;

import com.wf.captcha.ArithmeticCaptcha;
import com.wf.captcha.SpecCaptcha;
import com.wf.captcha.base.Captcha;
import javafx.scene.image.Image;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.ByteArrayInputStream;
import java.util.Base64;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
import java.util.concurrent.ConcurrentHashMap;

public class CaptchaService {
    private static final Logger logger = LoggerFactory.getLogger(CaptchaService.class);
    
    // 存储验证码和对应的答案
    private static final Map<String, String> CAPTCHA_STORE = new ConcurrentHashMap<>();
    
    // 验证码配置
    private static final int CAPTCHA_WIDTH = 120;
    private static final int CAPTCHA_HEIGHT = 40;
    private static final int CAPTCHA_LENGTH = 4;
    
    /**
     * 验证码结果
     */
    public static class CaptchaResult {
        private final String captchaId;
        private final Image image;
        private final String answer;
        
        public CaptchaResult(String captchaId, Image image, String answer) {
            this.captchaId = captchaId;
            this.image = image;
            this.answer = answer;
        }
        
        public String getCaptchaId() { return captchaId; }
        public Image getImage() { return image; }
        public String getAnswer() { return answer; }
    }
    
    /**
     * 生成图形验证码
     */
    public static CaptchaResult generateImageCaptcha() {
        try {
            // 创建字符验证码
            SpecCaptcha captcha = new SpecCaptcha(CAPTCHA_WIDTH, CAPTCHA_HEIGHT, CAPTCHA_LENGTH);
            
            // 设置验证码样式
            captcha.setCharType(Captcha.TYPE_DEFAULT);
            
            // 获取验证码文本（答案）
            String captchaText = captcha.text().toLowerCase();
            
            // 生成Base64图片
            String base64Image = captcha.toBase64();
            
            // 移除Base64前缀
            String imageData = base64Image.substring(base64Image.indexOf(",") + 1);
            
            // 解码Base64为字节数组
            byte[] imageBytes = Base64.getDecoder().decode(imageData);
            
            // 创建JavaFX Image
            Image image = new Image(new ByteArrayInputStream(imageBytes));
            
            // 生成唯一ID
            String captchaId = UUID.randomUUID().toString();
            
            // 存储验证码答案
            CAPTCHA_STORE.put(captchaId, captchaText);
            
            logger.debug("生成图形验证码: ID={}, 答案={}", captchaId, captchaText);
            
            return new CaptchaResult(captchaId, image, captchaText);
            
        } catch (Exception e) {
            logger.error("生成图形验证码失败", e);
            throw new RuntimeException("生成验证码失败", e);
        }
    }
    
    /**
     * 生成算术验证码
     */
    public static CaptchaResult generateArithmeticCaptcha() {
        try {
            // 创建算术验证码
            ArithmeticCaptcha captcha = new ArithmeticCaptcha(CAPTCHA_WIDTH, CAPTCHA_HEIGHT);
            
            // 设置算术表达式长度
            captcha.setLen(2); // 例如: 1+2=?
            
            // 获取算术表达式和答案
            String arithmeticString = captcha.getArithmeticString(); // 例如: "1+2=?"
            String captchaText = captcha.text(); // 计算结果，例如: "3"
            
            // 生成Base64图片
            String base64Image = captcha.toBase64();
            String imageData = base64Image.substring(base64Image.indexOf(",") + 1);
            byte[] imageBytes = Base64.getDecoder().decode(imageData);
            Image image = new Image(new ByteArrayInputStream(imageBytes));
            
            // 生成唯一ID
            String captchaId = UUID.randomUUID().toString();
            
            // 存储验证码答案
            CAPTCHA_STORE.put(captchaId, captchaText);
            
            logger.debug("生成算术验证码: ID={}, 表达式={}, 答案={}", captchaId, arithmeticString, captchaText);
            
            return new CaptchaResult(captchaId, image, captchaText);
            
        } catch (Exception e) {
            logger.error("生成算术验证码失败", e);
            throw new RuntimeException("生成验证码失败", e);
        }
    }
    
    /**
     * 验证验证码
     */
    public static boolean validateCaptcha(String captchaId, String userInput) {
        if (captchaId == null || userInput == null) {
            return false;
        }
        
        String correctAnswer = CAPTCHA_STORE.get(captchaId);
        if (correctAnswer == null) {
            logger.warn("验证码不存在或已过期: ID={}", captchaId);
            return false;
        }
        
        // 验证后移除验证码（一次性使用）
        CAPTCHA_STORE.remove(captchaId);
        
        // 忽略大小写和空格比较
        boolean isValid = correctAnswer.equalsIgnoreCase(userInput.trim());
        
        logger.debug("验证验证码: ID={}, 用户输入={}, 正确答案={}, 结果={}", 
                    captchaId, userInput, correctAnswer, isValid);
        
        return isValid;
    }
    
    /**
     * 获取验证码答案（用于调试）
     */
    public static String getCaptchaAnswer(String captchaId) {
        return CAPTCHA_STORE.get(captchaId);
    }
    
    /**
     * 清理过期的验证码（可定时调用）
     */
    public static void cleanupExpiredCaptchas() {
        // 这里可以实现定时清理逻辑
        // 生产环境建议使用Redis并设置过期时间
        int initialSize = CAPTCHA_STORE.size();
        // 可以添加基于时间的清理逻辑
        logger.debug("清理前验证码数量: {}", initialSize);
    }
}